<div style="width: 230px;    margin-top: 5px; margin-bottom: 5px;">
 <div class="input-group">
  <select id="taxolbanno" name="taxolbanno" style="width: 185px" class='taxolb'  autocomplete="off"> </select>
    <span class="input-group-btn">
        <button class="btn btn-default btn-sm" type="button"  data-toggle="modal" data-target="#TaxoModal" data-mytargetid="taxolbanno" title="Search on Taxonomy Tree">
            <span id=OpenTaxoLB class="glyphicon glyphicon-th-list" aria-hidden="true"/></button>
        </span>
    <span class="input-group-btn">
        <button class="btn btn-default btn-sm" type="button" title="Ctrl+D shortcut can also be utilized to assign category name to one or more vignettes" onclick="AssignTaxoLbToSelection();">
            <span id=AssignTaxo class="glyphicon glyphicon-tags" aria-hidden="true"/></button>
        </span>

{# <div style="line-height: 1.1;position: relative; top: -5px; height: 18px;cursor: pointer;">#}
{#<span class="label label-info" style="padding: 0px 3px 0px 3px; ; margin-left: 2px;" title="Update Counter" onclick="RefreshClassifTab();">UC</span><br>#}
{#        <span class="label label-info" style="padding: 0px 3px 0px 3px; ; margin-left: 2px;" title="Hide Empty Category" onclick="ToggleZeroCount();">HC</span></div>#}

 </div><!-- /input-group -->

</div>

<div id='divclassiftab' style="width: 255px;overflow-y:auto;">
<table class="classiftab" width="98%">
{% for v in res %}
<tr>
<td data-taxoid="{{ v['id'] }}" data-dispname="{{ v['display_name'] }}" class="{{  v['parentclasses'] }} {{ 'zerocount' if v['nbr']==0  }}">
 {% if v['haschild'] %}
 <small><span style="width: 1em;"  class="glyphicon glyphicon-triangle-bottom categexpander" ></span></small>
 {% endif %}
  <span class="taxodrop {% if v['haschild'] %}haschild{% endif %}" style="margin-left: {{ (0 if v['haschild'] else 1)+ v['dist']*0.9 }}em">
    {{ v['htmldisplayname'] }}
</span>
<span class="taxoparent">{{ v['taxoparent']|safe }}</span>

<div class="counterarea">
  <span class="counter label label-success">{{ v['nbr_v'] }}</span>
 {% if v['nbr_p']>0 %}
  <span class="counternotv label label-info">{{v['nbr_p']}}</span>
 {% endif %}
 {% if v['nbr_d']>0 %}
  <span class="counternotv label label-warning">{{v['nbr_d']}}</span>
 {% endif %}
</div>
</td>
</tr>
{% endfor %}
</table>
<div style="margin-top: 3px;">
<a href="javascript:RefreshClassifTab('Y');" class="btn btn-primary btn-xs" style="width: 45%;" title="It may slow the application. Please use the UC (update count) button instead">更新计数 <span class="glyphicon glyphicon-repeat"></span></a>
<button type="button" class="btn btn-xs btn-primary" id="zeroshowhide" onclick="ToggleZeroCount()" data-show="0">隐藏空的分类目录</button>

</div>

  </div>

<script>
  function SetTaxoFilter(taxofiltervalue,taxofilterlabel,withchild){
    //debugger;
    var WithChild='N';
    if(withchild==true){
      taxofilterlabel+=" (with child)";
      WithChild='Y';
    }
    if(taxofiltervalue==false){
      $("#taxofilter").val("");
      $("#taxofilterlabel").val("");
      if(taxofilterlabel==-1) LoadRightPane();
      return;
    }
    $("#taxofilter").val(taxofiltervalue);
    $("#taxofilterlabel").val(taxofilterlabel);
    $("#taxofilterchild").val(WithChild);


  }
function CategExpanderClick(e){
    e.stopPropagation();
    e.preventDefault();
    if($(this).hasClass("glyphicon-triangle-bottom")){
        $(this).removeClass("glyphicon-triangle-bottom").addClass("glyphicon-triangle-right");
        $('#divclassiftab .visib'+$(this).closest("td").data("taxoid")).hide();
    }
    else {
        $(this).removeClass("glyphicon-triangle-right").addClass("glyphicon-triangle-bottom");
        $('#divclassiftab .visib'+$(this).closest("td").data("taxoid")).show();

    }

}

{% if g.PrjAnnotate %}
    {# Traitement de la Liste des objets TD à traiter. #}
    function ProcessList(LstTd,droptaxoid,droptaxoname) {
        var TrSet = new Set(),i;
        PendingChangesTaxoName[droptaxoid]=droptaxoname;
        var taxopart=droptaxoname.split('<');
        var HtmlTaxo="<span class='cat_name'>"+taxopart[0]+"</span>";
        if(taxopart.length>1){
          HtmlTaxo+="<span class='cat_ancestor'>";
          for(i= 1; i < taxopart.length; i++)
            HtmlTaxo+=" &lt;&nbsp;"+taxopart[i];
          HtmlTaxo+="</span>";
        }

        // Traitement des cellules
          for(i= 0; i < LstTd.length; i++) {
              var td=LstTd[i];
              td.removeClass("ui-selected");
              td.addClass("ToBeSaved");
              var id = td.find('img').attr('id');
              td.find('.taxo').html(HtmlTaxo);
              td.find('.subimg').css("height",'').css("width",'').css("left",'').css("top",'').css("right",'').css("bottom",'');
              td.find('.subimg').attr('class','subimg status-validated');
              TrSet.add(td.closest('tr').attr('id'));
              PendingChanges[id.substr(1)]=droptaxoid;
              //td.css('background-color', '#80FF80')
              //console.log(o, id ,droptaxoid,droptaxoname);
          }
          UpdateSelectedCounter();
          NbrChanged=LstTd.length;
          // Ces resizes ralentissent mais permettent de recaller les zoom tracker suite au changement de taille des taille de taxo
          // sur table 1000 image à 10% ligne 42 ca Freeze 4s
          // sur table 200 images à 10% ca Freeze 1s
          // Sur 50&100 ca ne se voit pas
          //for ( trid of TrSet) Marche pas sous IE
          TRArray=Array.from(TrSet);
          for(i= 0; i < TRArray.length; i++)
          {
              var trid=TRArray[i];
              $('#' + trid).find('td img').resize();
              //console.log("resize #"+trid);
          }
        var calctotaux={};
        for (var k in PendingChanges) {
            v=0;
            if (PendingChanges[k] in calctotaux) v=calctotaux[PendingChanges[k]];
            calctotaux[PendingChanges[k]]=v+1;
        }
        var Msg="Pending Changes : ";
        PendingChangesTaxoName[-1]="Unchanged";
        for (k in calctotaux)
            Msg=Msg+calctotaux[k]+" "+PendingChangesTaxoName[k]+", ";
        $('.PendingChangesClass').text(Msg);
        document.getElementById("BtnSave").disabled = false;
        $("#TxtBtnValidateAll").text("Save changes, validate rest and move to next page");
    }
function SavePendingChanges(NextPage,forcedqual) {
    {#  console.log("prev",PendingChanges); #}
    req={changes:PendingChanges,qual:((forcedqual===undefined)?'V':forcedqual)}
    $(".PendingChangesClass").html('<span class="label label-info">Server update in progress...</span>');
    $("#PendingChanges2").html($("#PendingChanges").html());
    $("#PendingChanges").load("/prj/ManualClassif/"+$("#projid").val(),req,function(){
        $("#PendingChanges2").html($("#PendingChanges").html());
        if ($("#PendingChanges").html().indexOf("Successfull")>0) {
            PendingChanges={}; // After successfull update no pending changes.
            if(NextPage==1)
               $("#pageoffset").val(parseInt($("#pageoffset").val())+1);
            else {# Si on ne change pas de page on garde l'offset de la scrollbar vertical à sa position courante #}
                if(NextPage===0) {} {# Distinction entre save et save go to next page qui en fait reste sur la page. #}
                else
                  RightPanelScrollPosAfterLoad=$(document).scrollTop();
            LoadRightPane();
            RefreshClassifTab();
        }
    });
}
function ValidateAll(NextPage) {
    {# On valide tout ce qui est predicted ou validated et qui n'est pas déjà en attente de save #}
    $(".status-validated,.status-predicted").parents('td').find('img.lazy').each(function (e,o) {
        //console.log($(o).attr("id").substr(1));
        if(PendingChanges[$(o).attr("id").substr(1)]===undefined)
            PendingChanges[$(o).attr("id").substr(1)]=-1; {# Set unchanged but validate #}
    });
    SavePendingChanges(NextPage);
}
function ValidateSelection(qual) {
    {# On valide tout ce qui est selectionné et qui n'est pas déjà en attente de save #}
    $(".ui-selected").find('img.lazy').each(function (e,o) {
        if(PendingChanges[$(o).attr("id").substr(1)]===undefined)
            PendingChanges[$(o).attr("id").substr(1)]=-1; {# Set unchanged but validate #}
    });
    SavePendingChanges(0,qual);
}

{% endif %}
  $(function() {
    $( ".classiftab td"
{% if g.PrjAnnotate %}
    ).droppable({
      tolerance: "pointer",
{#      classes:{"ui-droppable-hover":"taxodrop_hover"}, Utile pour JQuery UI >=1.12 car hoverClass deprecated#}
      hoverClass: "taxodrop_hover",
      drop: function( event, ui ) {
          var droptaxoid=$(this).data('taxoid');
          var droptaxoname=$(this).data('dispname');
          var jtaxolbanno=$('#taxolbanno');
         jtaxolbanno.append($('<option>', {    value: droptaxoid,    text: droptaxoname}));
          var sel=[];
          sel.push(droptaxoid);
          jtaxolbanno.val(sel);
          jtaxolbanno.change();
          var NbrChanged=0;
          var  LstTd=[];
          ui.draggable.each(function (e,o) {
              NbrChanged++;
              if( $(o).hasClass( "zoomtracker" )) {
                  LstTd.push(  $($(o).data("specs").origImg.closest('td')));
{#              } else if( $(o).hasClass( "taxo" )) {  // Sinon c'est le taxo du div subimg#}
              } else if( $(o).is( "td" )) {  // Sinon c'est le taxo du div subimg
                  LstTd.push(  $(o));
              } else if( $(o).hasClass( "lazy" )) {  // Sinon c'est l'image
                  LstTd.push(  $(o).closest('td'));
              }
              //Si c'est un item selected, on le supprime car va être ajouté par
              if(LstTd.length>0)
                if(LstTd[0].hasClass( "ui-selected" ))
                    LstTd.pop();
              // On ajoute tout ceux qui sont selectionnés.
              $(".ui-selected").each(function(){LstTd.push($(this));NbrChanged++;});
          });
        ProcessList(LstTd,droptaxoid,droptaxoname);
        // Highlight only the last
        $( "#TabA .ui-state-highlight").removeClass( "ui-state-highlight");
        var n=  parseInt($( this ).find( ".counter").text())||0;
        $( this ).addClass( "ui-state-highlight" ).find( ".counter" ).html(n+NbrChanged );
      }
    }
{% endif %}
    ).click(function() {
        $(".ui-state-highlight").removeClass("ui-state-highlight");
        if ($(this).hasClass('activeTaxo'))
            SetTaxoFilter(false, -1);
        else {
        SetTaxoFilter($(this).data('taxoid'), $(this).find('.taxodrop').text());
        LoadRightPane();
        }
    });

    $("#divclassiftab").outerHeight( $("#column-left").innerHeight()-$("#divclassiftab").position().top );
    $("#divclassiftab .categexpander").click(CategExpanderClick).hover(function(e){
        if((DragInProgress)&&($(this).hasClass("glyphicon-triangle-right"))) {
            {# Quand on passe sur un triange fermé sur un Drag&Drop on simule un clic sur le triangle pour l'ouvrir #}
            $(this).click();
        }
    });
  }); {# Ready #}

{% if g.PrjAnnotate %}
function AssignTaxoLbToSelection() {
    var droptaxoid = $('#taxolbanno').val();
    if (droptaxoid) {
        $(".ui-state-highlight").removeClass("ui-state-highlight");
        $("td[data-taxoid='"+$('#taxolbanno').val()+"']").addClass( "ui-state-highlight" );
        var LstTd = [];
        $(".ui-selected").each(function () {
            LstTd.push($(this));
        });
        ProcessList(LstTd, droptaxoid, $('#taxolbanno  option:selected').text());
    }
}

$(document).ready(function() {
    EnableSelect2Taxolb();
{#    Restore le surlignage jaune dans l'arbre #}
    if(typeof(RestoreHighLigthID)!=='undefined'){
      $('td[data-taxoid='+RestoreHighLigthID+']').addClass('ui-state-highlight');
      RestoreHighLigthID=undefined;
    }
{#    Restore le surlignage Gris dans l'arbre/activeTaxo pour filtrage #}
    if(typeof(RestoreActiveTaxoID)!=='undefined'){
      $('td[data-taxoid='+RestoreActiveTaxoID+']').addClass('activeTaxo');
      RestoreActiveTaxoID=undefined;
    }
{#    Le fait de choisir un item fait l'assignation/CTRL+A#}
    $('#taxolbanno').on("select2:select", function (e) {
        AssignTaxoLbToSelection();
    });

{# Gestion de la scrollbar de la liste taxo quand la souris est en bas ou en haut de la zone#}
$(window).mousemove(function (e) {
  var divclassiftab=$('#divclassiftab');
  var pagebottom=$(this).scrollTop()+$(this).innerHeight()-50;
  if(e.pageX<235)
  {
    if(e.pageY>pagebottom)
      divclassiftab.scrollTop(divclassiftab.scrollTop()+10);
    if((e.pageY>divclassiftab.offset().top)&&(e.pageY<divclassiftab.offset().top+25)&&(e.pageX>180))
      divclassiftab.scrollTop(divclassiftab.scrollTop()-10);
  }
  });

}); // Ready

{% endif %} {# if g.PrjAnnotate #}

var taxotree={{ taxotree|safe }};

$(document).ready(function() {
  {#  Initialisation Context Menu  #}
  $.contextMenu({
  // define which elements trigger this menu
  selector: ".classiftab td",
  // define the elements of the menu
  build: function($trigger, e) {
    res= {
      callback: function (key, options) {
        var prefix=key.substr(0,1);
        if(prefix==='X') return; {# Menu informatifs #}
        var taxoid=parseInt(key.substr(1));
        var taxoname=taxotree[taxoid][1];
        if(prefix==='f') {
{#          console.log("filter by ",taxoid,taxoname);#}
          SetTaxoFilter(taxoid,taxoname,true);
          LoadRightPane();
        }
        if(prefix==='o') {
          $('#taxolbanno').append($('<option>', {value: taxoid, text: taxoname}));
          var sel = [];
          sel.push(taxoid);
          $('#taxolbanno').val(sel).change();
          AssignTaxoLbToSelection();
        }
      },
      items: {}
    };
    var Arr=[];
    var taxoid=$(e.currentTarget).data('taxoid');
    var taxoname=taxotree[taxoid][1];
    Arr.unshift({key:"f"+taxoid,name:taxoname});
{#     On insere d'abord en bas le filtrage #}
    for(var i=0;i<50;i++) {
        taxoid=taxotree[taxoid][2]; // Go to parent
        if (taxoid==null) break;
        taxoname=taxotree[taxoid][1];
        Arr.unshift({key:"f"+taxoid,name:taxoname})
    }
    Arr.unshift({key:"X2",name:"-- FILTER WITH CHILD -- "});
    Arr.unshift({key:"X1",name:"_____________________"});

    taxoid=$(e.currentTarget).data('taxoid');
    taxoname=$(e.currentTarget).find(".taxodrop").text();
    Arr.unshift({key:"o"+taxoid,name:taxoname})
    for(i=0;i<50;i++) {
        taxoid=taxotree[taxoid][2]; // Go to parent
        if (taxoid==null) break;
        taxoname=taxotree[taxoid][1];
        Arr.unshift({key:"o"+taxoid,name:taxoname})
    }
    Arr.unshift({key:"X3",name:"-- CLASSIFY TO -- "});

    for	(index = 0; index < Arr.length; index++)
        res["items"][Arr[index]["key"]]={name:Arr[index]["name"]}
    return res;
    }
  }); {#  Initialisation Context Menu  #}
}); {#  Ready  #}

function ToggleZeroCount(){
    if($('#zeroshowhide').data("show")=="0") {
        $(".zerocount").hide();
        $('#zeroshowhide').data("show","1").text("显示空的分类");
    }
    else {
        $('#zeroshowhide').data("show", "0").text("隐藏空的分类");
        $(".zerocount").show();
    }
}


</script>
